home *** CD-ROM | disk | FTP | other *** search
/ The X-Philes (2nd Revision) / The X-Philes Number 1 (1995).iso / xphiles / hp95 / freyja_t.z / freyja_t / misc.c < prev    next >
C/C++ Source or Header  |  1992-04-14  |  10KB  |  595 lines

  1. /* MISC.C -- Miscellaneous Commands
  2.  
  3.     Written July 1991 by Craig A. Finseth
  4.     Copyright 1991 by Craig A. Finseth
  5. */
  6.  
  7. #include "freyja.h"
  8.  
  9. void M_Change();    /* char *oldstr, char *newstr, char *savestr */
  10. void M_Replace();    /* FLAG isquery */
  11. FLAG M_Search();    /* char *str, FLAG isforward */
  12.  
  13. /* ------------------------------------------------------------ */
  14.  
  15. /* Move backward to grayspace. */
  16.  
  17. void
  18. GoToGrayB()
  19.     {
  20.     MoveToB(IsGray);
  21.     }
  22.  
  23.  
  24. /* ------------------------------------------------------------ */
  25.  
  26. /* Move forward to grayspace. */
  27.  
  28. void
  29. GoToGrayF()
  30.     {
  31.     MoveToF(IsGray);
  32.     }
  33.  
  34.  
  35. /* ------------------------------------------------------------ */
  36.  
  37. /* Move backward to. */
  38.  
  39. void
  40. GoToNotGrayB()
  41.     {
  42.     MovePastB(IsGray);
  43.     }
  44.  
  45.  
  46. /* ------------------------------------------------------------ */
  47.  
  48. /* Move forward to non-grayspace. */
  49.  
  50. void
  51. GoToNotGrayF()
  52.     {
  53.     MovePastF(IsGray);
  54.     }
  55.  
  56.  
  57. /* ------------------------------------------------------------ */
  58.  
  59. /* Tell if the current character is a newline. */
  60.  
  61. FLAG
  62. IsNL()
  63.     {
  64.     char chr;
  65.  
  66.     chr = BGetChar();
  67.     return(chr == NL || chr == SNL);
  68.     }
  69.  
  70.  
  71. /* ------------------------------------------------------------ */
  72.  
  73. /* Tell if the current character is gray space. */
  74.  
  75. FLAG
  76. IsGray()
  77.     {
  78.     char chr;
  79.  
  80.     chr = BGetChar();
  81.     return(chr == SP || chr == TAB || chr == NL || chr == SNL);
  82.     }
  83.  
  84.  
  85. /* ------------------------------------------------------------ */
  86.  
  87. /* Tell if the current character is whitespace. */
  88.  
  89. FLAG
  90. IsWhite()
  91.     {
  92.     char chr;
  93.  
  94.     chr = BGetChar();
  95.     return(chr == SP || chr == TAB);
  96.     }
  97.  
  98.  
  99. /* ------------------------------------------------------------ */
  100.  
  101. /* Abort the current command prefix. */
  102.  
  103. void
  104. MAbort()
  105.     {
  106.     TBell();
  107.     DModeLine();
  108.     uarg = 0;
  109.     }
  110.  
  111.  
  112. /* ------------------------------------------------------------ */
  113.  
  114. /* Handle the Control-X prefix. */
  115.  
  116. void
  117. MCtrlX()
  118.     {
  119.     FLAG disp;
  120.  
  121.     disp = KDelayPrompt("Control-X:");
  122.     table = TabTable(key, table);
  123.     key = KGetChar();
  124.     if (disp) DModeLine();
  125.     TabDispatch(key, table);
  126.     }
  127.  
  128.  
  129. /* ------------------------------------------------------------ */
  130.  
  131. /* Exit the editor. */
  132.  
  133. void
  134. MExit()
  135.     {
  136.     struct buffer *bptr;
  137.     int k;
  138.  
  139.     uarg = 0;
  140.     for (bptr = buffers; bptr < &buffers[NUMBUFFERS]; bptr++) {
  141.         if (!BIsFree(bptr) && !IS_SYS(bptr->fname) && BIsMod(bptr)) {
  142.             BBufGoto(bptr);
  143.             DIncrDisplay();
  144.             k = KAsk("Save before exiting? ");
  145.             if (k == KEYABORT) {
  146. #if defined(SYSMGR)
  147.                 JNoFini();
  148. #endif
  149.                 return;
  150.                 }
  151.             else if (k == KEYQUIT) BFileWrite();
  152.             else if (k == 'Y' && !BFileWrite()) return;
  153.             }
  154.         }
  155.     doabort = TRUE;
  156.     }
  157.  
  158.  
  159. /* ------------------------------------------------------------ */
  160.  
  161. /* Insert the arg. */
  162.  
  163. void
  164. MIns8()
  165.     {
  166.     if (!isuarg) {
  167.         DError("An explicit argument must be supplied.");
  168.         }
  169.     else    {
  170.         BInsChar(uarg);
  171.         }
  172.     uarg = 0;
  173.     }
  174.  
  175.  
  176. /* ------------------------------------------------------------ */
  177.  
  178. /* Self-insert. */
  179.  
  180. void
  181. MInsChar()
  182.     {
  183.     struct mark *mptr;
  184.  
  185.     if (cbuf->c.fill == 'F' && BGetCol() >= cbuf->c.right_margin) {
  186.         mptr = BMarkCreate();
  187.         do    {
  188.             GoToGrayB();
  189.             MovePastB(IsWhite);
  190.             } while (BGetCol() > cbuf->c.right_margin);
  191.         if (BGetCol() == 0) {
  192.             MovePastF(IsWhite);
  193.             GoToGrayF();
  194.             }
  195.         if (BIsBeforeMark(mptr)) {
  196.             MovePastF(IsWhite);
  197.             BMoveBy(-1);
  198.             BCharChange(NL);
  199.             BInsSpaces(cbuf->c.left_margin);
  200.             if (BIsBeforeMark(mptr)) BPointToMark(mptr);
  201.             }
  202.         else    BPointToMark(mptr);
  203.         BMarkDelete(mptr);
  204.         }
  205.     BInsChar(key);
  206.     }
  207.  
  208.  
  209. /* ------------------------------------------------------------ */
  210.  
  211. /* Make the previous command a deletion command. */
  212.  
  213. void
  214. MMakeDelete()
  215.     {
  216.     }
  217.  
  218.  
  219. /* ------------------------------------------------------------ */
  220.  
  221. /* Handle the Meta prefix. */
  222.  
  223. void
  224. MMeta()
  225.     {
  226.     FLAG disp;
  227.  
  228.     disp = KDelayPrompt("Meta:");
  229.     table = TabTable(key, table);
  230.     key = KGetChar();
  231.     if (disp) DModeLine();
  232.     TabDispatch(key, table);
  233.     }
  234.  
  235.  
  236. /* ------------------------------------------------------------ */
  237.  
  238. /* Not implemented. */
  239.  
  240. void
  241. MNotImpl()
  242.     {
  243.     DError("Unknown command");
  244.     uarg = 0;
  245.     }
  246.  
  247.  
  248. /* ------------------------------------------------------------ */
  249.  
  250. /* Quote the next character. */
  251.  
  252. void
  253. MQuote()
  254.     {
  255.     FLAG disp;
  256.     int c;
  257.  
  258.     disp = KDelayPrompt("Quote:");
  259.     c = KGetChar();
  260.     while (uarg-- > 0) {
  261.         BInsChar(c);
  262.         }
  263.     if (disp) DModeLine();
  264.     uarg = 0;
  265.     }
  266.  
  267.  
  268. /* ------------------------------------------------------------ */
  269.  
  270. /* Replace string. */
  271.  
  272. void
  273. MReplace()
  274.     {
  275.     M_Replace(FALSE);
  276.     }
  277.  
  278.  
  279. /* ------------------------------------------------------------ */
  280.  
  281. /* Query replace string. */
  282.  
  283. void
  284. MReplaceQ()
  285.     {
  286.     M_Replace(TRUE);
  287.     }
  288.  
  289.  
  290. /* ------------------------------------------------------------ */
  291.  
  292. /* Backward string search. */
  293.  
  294. void
  295. MSearchB()
  296.     {
  297.     if (KGetStr("Reverse Search", stringarg, sizeof(stringarg)) != 'Y') {
  298.         uarg = 0;
  299.         return;
  300.         }
  301.     BMarkToPoint(cwin->point);
  302.     while (uarg-- > 0) {
  303.         if (!M_Search(stringarg, BACKWARD)) {
  304.             BPointToMark(cwin->point);
  305.             DError("String not found");
  306.             break;
  307.             }
  308.         }
  309.     uarg = 0;
  310.     }
  311.  
  312.  
  313. /* ------------------------------------------------------------ */
  314.  
  315. /* Forward string search. */
  316.  
  317. void
  318. MSearchF()
  319.     {
  320.     if (KGetStr("Forward Search", stringarg, sizeof(stringarg)) != 'Y') {
  321.         uarg = 0;
  322.         return;
  323.         }
  324.     BMarkToPoint(cwin->point);
  325.     while (uarg-- > 0) {
  326.         if (!M_Search(stringarg, FORWARD)) {
  327.             BPointToMark(cwin->point);
  328.             DError("String not found");
  329.             break;
  330.             }
  331.         }
  332.     uarg = 0;
  333.     }
  334.  
  335.  
  336. /* ------------------------------------------------------------ */
  337.  
  338. /* Handle argument prefix. */
  339.  
  340. void
  341. MUArg()
  342.     {
  343.     FLAG numflag = FALSE;
  344.     FLAG wasechoed;
  345.  
  346.     uarg *= 4;
  347.     wasechoed = KUArg(uarg);
  348.     while (xisdigit(key = KGetChar()))  {
  349.         if (!numflag) {
  350.             uarg = 0;
  351.             numflag = TRUE;
  352.             }
  353.         uarg = uarg * 10 + key - '0';
  354.         wasechoed |= KUArg(uarg);
  355.         }
  356.  
  357.     if (wasechoed) DModeLine();
  358.     isuarg = TRUE;
  359.     TabDispatch(key, table);
  360.     }
  361.  
  362.  
  363. /* ------------------------------------------------------------ */
  364.  
  365. /* Move back past a type of text. */
  366.  
  367. void
  368. MovePastB(pred)
  369.     FLAG (*pred)();
  370.     {
  371.     BMoveBy(-1);
  372.     while (!BIsStart() && (*pred)()) BMoveBy(-1);
  373.     if (!BIsStart()) BMoveBy(1);
  374.     }
  375.  
  376.  
  377. /* ------------------------------------------------------------ */
  378.  
  379. /* Move forward past a type of text. */
  380.  
  381. void
  382. MovePastF(pred)
  383.     FLAG (*pred)();
  384.     {
  385.     while (!BIsEnd() && (*pred)()) BMoveBy(1);
  386.     }
  387.  
  388.  
  389. /* ------------------------------------------------------------ */
  390.  
  391. /* Move back to a type of text. */
  392.  
  393. void
  394. MoveToB(pred)
  395.     FLAG (*pred)();
  396.     {
  397.     BMoveBy(-1);
  398.     while (!BIsStart() && !(*pred)()) BMoveBy(-1);
  399.     if (!BIsStart()) BMoveBy(1);
  400.     }
  401.  
  402.  
  403. /* ------------------------------------------------------------ */
  404.  
  405. /* Move forward to a type of text. */
  406.  
  407. void
  408. MoveToF(pred)
  409.     FLAG (*pred)();
  410.     {
  411.     while (!BIsEnd() && !(*pred)()) BMoveBy(1);
  412.     }
  413.  
  414.  
  415. /* ------------------------------------------------------------ */
  416.  
  417. /* Reverse search for the next newline. */
  418.  
  419. FLAG
  420. SearchNLB()
  421.     {
  422.     return(BSearchB(NL, SNL));
  423.     }
  424.  
  425.  
  426. /* ------------------------------------------------------------ */
  427.  
  428. /* Search for the next newline. */
  429.  
  430. FLAG
  431. SearchNLF()
  432.     {
  433.     return(BSearchF(NL, SNL));
  434.     }
  435.  
  436.  
  437. /* ------------------------------------------------------------ */
  438.  
  439. /* Change old string into new */
  440.  
  441. void
  442. M_Change(oldstr, newstr, savestr)
  443.     char *oldstr;
  444.     char *newstr;
  445.     char *savestr;
  446.     {
  447.     int newlen = strlen(newstr);
  448.     int oldlen = strlen(oldstr);
  449.     int cnt;
  450.  
  451.     BMoveBy(-oldlen);
  452.     if (savestr != NULL) {
  453.         for (cnt = 0; cnt < oldlen; ++cnt) {
  454.             *savestr++ = BGetCharAdv();
  455.             }
  456.         *savestr = NUL;
  457.         BMoveBy(-oldlen);
  458.         }
  459.     if (oldlen > newlen) BCharDelete(oldlen - newlen);
  460.  
  461.     cnt = min(oldlen, newlen);
  462.     while (cnt-- > 0) BCharChange(*newstr++);
  463.  
  464.     while (*newstr != NUL) BInsChar(*newstr++);
  465.     }
  466.  
  467.  
  468. /* ------------------------------------------------------------ */
  469.  
  470. /* Do query replace and replace string */
  471.  
  472. void
  473. M_Replace(isquery)
  474.     FLAG isquery;
  475.     {
  476.     int key;
  477.     char from[STRMAX];
  478.     char to[STRMAX];
  479.     char save[STRMAX];
  480.     char buf[LINEBUFFSIZE];
  481.     struct mark *mptr;
  482.  
  483.     uarg = 0;
  484.     *from = NUL;
  485.     *to = NUL;
  486.  
  487.     do    {
  488.         if (KGetStr(isquery ? "Query Replace String" :
  489.             "Replace String", from, sizeof(from)) != 'Y') return;
  490.         } while (*from == NUL);
  491.     if (KGetStr("with", to, sizeof(to)) != 'Y') return;
  492.  
  493.     mptr = BMarkCreate();
  494.     key = isquery ? ',' : SP;
  495.  
  496.     xsprintf(buf, TMaxCol() < 60 ? "Repl '%s' w '%s'" :
  497.         "Replacing '%s' with '%s'", from, to);
  498.  
  499.     while (M_Search(from, FORWARD)) {
  500.         if (!isquery) {
  501.             M_Change(from, to, NULL);
  502.             continue;
  503.             }
  504.         DIncrDisplay();
  505.         DEchoNM(buf);
  506.         key = xtoupper(KGetChar());
  507.         if (key == KEYQUIT || key == KEYABORT || key == BEL ||
  508.              key == ESC) {
  509.             BMarkToPoint(mptr);
  510.             break;
  511.             }
  512.  
  513.         switch (key) {
  514.  
  515. #if defined(MSDOS)
  516.         case KEYHELP:
  517. #endif
  518.         case '?':
  519.             M_Search(from, BACKWARD);
  520.             DIncrDisplay();
  521.             DView("Commands are: Y)yes N)no ,)try !)all .)exit ;)do&exit");
  522.             key = ',';
  523.             break;
  524.  
  525.         case '!':
  526.             isquery = FALSE;
  527.         case SP:
  528.         case ',':        /* test comes later... */
  529.         case ';':
  530.         case 'Y':
  531.             M_Change(from, to, save);
  532.             DIncrDisplay();
  533.             if (key == ',' && KAsk("Confirm Replace?") != 'Y')
  534.                 M_Change(to, save, NULL);
  535.             if (key == ';') BMoveToEnd();
  536.             break;
  537.  
  538.         case '.':
  539.             BMoveToEnd();
  540.             break;
  541.  
  542.         case 'N':
  543.         case DEL:
  544.         case BS:
  545.             break;
  546.  
  547.         default:
  548.             TBell();
  549.             }
  550.         }
  551.     DModeLine();
  552.     BPointToMark(mptr);
  553.     BMarkDelete(mptr);
  554.     }
  555.  
  556.  
  557. /* ------------------------------------------------------------ */
  558.  
  559. /* Search for STR in the specified direction. */
  560.  
  561. FLAG
  562. M_Search(str, isforward)
  563.     char *str;
  564.     FLAG isforward;
  565.     {
  566.     int cnt;
  567.     char c1;
  568.     char c2;
  569.  
  570.     for (cnt = 0; str[cnt] != NUL; ) {
  571.         c1 = *str;
  572.         c2 = xtoupper(c1);
  573.         if (isforward) {
  574.             if (!BSearchF(c1, c2)) break;
  575.             }
  576.         else    {
  577.             if (!BSearchB(c1, c2)) break;
  578.             BMoveBy(1);
  579.             }
  580.  
  581.         for (cnt = 1; !BIsEnd() && str[cnt] != NUL; ++cnt) {
  582.             c1 = str[cnt];
  583.             c2 = xtoupper(c1);
  584.             if (BGetChar() != c1 && BGetChar() != c2) break;
  585.             BMoveBy(1);
  586.             }
  587.         if (!isforward || str[cnt] != NUL)
  588.             BMoveBy((isforward ? 1 : 0) - cnt);
  589.         }
  590.     return(str[cnt] == NUL);
  591.     }
  592.  
  593.  
  594. /* end of MISC.C -- Miscellaneous Commands */
  595.